home *** CD-ROM | disk | FTP | other *** search
- From: gregor@netcom.com (Greg Colvin)
- Message-ID: <gregorDpoGM2.Hw2@netcom.com>
- X-Original-Date: Thu, 11 Apr 1996 03:06:02 GMT
- Path: in2.uu.net!bounce-back
- Date: 11 Apr 96 08:05:39 GMT
- Approved: fjh@cs.mu.oz.au
- Newsgroups: comp.std.c++
- Subject: Re: sample auto_ptr template
- Organization: Netcom Online Communications Services (408-241-9760 login: guest)
- References: <009A0A5CE1159CC0.49802F14@ittpub.nl>
- X-Auth: PGPMoose V1.1 PGP comp.std.c++
- iQBFAgUBMWy90+EDnX0m9pzZAQEbagGAmUmhXMA9JJF1Q0F0Kumm8Hze34KKX6VW
- QrBDR5VwCUJbZ5Rg3Uj29BdLPAKoC2hk
- =3wCG
-
- In article <009A0A5CE1159CC0.49802F14@ittpub.nl> "Wil Evers" <wil@ittpub.nl>
- writes:
- >In article <gregorDpFBCt.A5@netcom.com> gregor@netcom.com (Greg
- >Colvin) writes:
- >
- >> Please remember that auto_ptr is designed to make sure that pointers
- >> are deleted when exceptions are thrown, not to be sure that already
- >> deleted pointers are not misused. The semantics of auto_ptr are
- >> intentionally "as close as possible" to ordinary pointers: if you
- >> use a pointer that is already deleted the behaviour is undefined,
- >> and the same for auto_ptr; if you use a pointer that is owned by
- >> another object (i.e. will be deleted by that objects destructor) the
- >> behaviour is well defined as long as the pointer remains valid, and
- >> the same for auto_ptr; you cannot tell at runtime whether a pointer
- >> is valid, and the same for auto_ptr.
- >
- >My original question was "Did the committee explicitly decide to allow
- >dereferencing of non-owning auto_ptrs? If so, what is the rationale
- >behind this?" It seems to me Greg's answer is "Yes, because that's
- >what ordinary pointers do." I cannot understand this. Why allow a
- >dangerous operation just because ordinary pointers do not prohibit it?
- >
- >Please note:
- >
- >1. The previous (April '95 DWP) incarnation of auto_ptr did not forbid
- >to have a second, non-owning, pointer to the owned object. However,
- >in order to get one, we had to explicitly call the get() member
- >function, which returns an ordinary pointer. In my opinion, requiring
- >the user to go through all this trouble was a reasonable safeguard
- >against accessing released memory and unintended aliasing. In the new
- >incarnation, there are no such guarantees: an auto_ptr silently
- >changes into a zombie pointer as a side effect of a copy operation.
- >
-
- Pre April, an auto_ptr silently changed into a null pointer after
- copying, except that trying to copy it was ill-formed. Post April
- copying is allowed. Derereferencing a null pointer gives undefined
- behavior, as does dereferencing a pointer to a deleted object, so I
- don't see such a big difference. Given
- void f(auto_ptr<T>);
- auto_ptr<T> p(px);
- then before April we had
- f(p); // unintentionally ill-formed
- p->whatever(); // undefined behavior
- and after April we have
- f(p); // well-formed
- p->whatever(); // possibly undefined behavior
-
- It is not hard to create a version of auto_ptr that throws an exception
- if the "zombie pointer" is dereferenced, at some cost in performance,
- and I hope vendors will provide such versions for debugging at least.
- If an implementation provides a garbage collector (which is hard) then
- providing a safer auto_ptr becomes fairly easy and cheap. Vendors are
- always allowed to define undefined behavior to something more useful.
-
- >2. We all have to pay the price for the committee's decision. The
- >new implementation is about twice as complicated - up to the point
- >where almost no existing compiler can handle it - and half as
- >efficient. Furthermore, dropping a guarantee always breaks existing
- >code.
-
- Actually, no compiler has ever been able to compile any version of
- auto_ptr, since they all have used member templates.
-
- My implementation of auto_ptr is not, IMHO, significantly more
- complicated that before (one more member and a few tests, no big
- deal). The complication has always been in the member templates.
-
- >
- >What I definitely do not understand is why the new auto_ptr template
- >doesn't even allow us to query if it is actually owning the object
- >pointed to.
- >
-
- This was a hard call, and I'm open to suggestions. Adding a mutable
- member to a class is never pretty, but making the member visible in any
- way is ugly: I don't like for a const argument to change its value,
- and I think of the value of an object as being whatever its public
- interface reveals. Thus, I find "mutable bool owner" just barely
- tolerable, and "bool is_owner() { return owner;} " quite distasteful.
-
- As a practical matter, I can imagine implementations of auto_ptr that
- do not store the ownership in the auto_ptr, but perhaps in the bowels
- of an OS provided garbage collection system, such that is_owner() might
- be very hard to implement efficiently.
-
- Also, I found it very hard to contrive examples where is_owner() would
- actually be useful. I think most such examples would involve passing a
- reference to an auto_ptr to a function that may or may not then take
- ownership. In that case, the callee can always zero out the auto_ptr
- argument itself. An alternative idiom is:
- template<typename T> auto_ptr<T> source_sink(auto_ptr<T>);
- ...
- p = source_sink(p);
- if (&*p)
- ...
-
- >> What you can do is design your code so that you know who owns each
- >> object when. The auto_ptr template can help you implement such
- >> designs safely. If you cannot design your code to work with
- >> auto_ptr you probably need garbage collection of some form.
- >
- >auto_ptr may have been designed to provide only limited functionality,
- >but since it is the only heap object management facility in the
- >standard, it will be used in many different contexts. Therefore, I
- >think it is quite resonable to ask how easy it is to abuse it. What I
- >dislike about the new auto_ptr incarnation is that it is even easier
- >to abuse
-
- I still think that being able to tell who owns an auto_ptr will lead even
- more "abuse", since if need to ask you will inevitably forget to ask, and
- crash as a result. And if you need to know, then your design is probably
- not appropriate for an auto_ptr<> anyway. Don't ask, don't tell.
-
- If anyone can think of examples where an is_owner() is really required
- please let me know. A workable fudge might be a protected is_owner(),
- so that you have to work at abusing it.
-
- Greg Colvin
- gregor@netcom.com
- ---
- [ comp.std.c++ is moderated. To submit articles: try just posting with ]
- [ your news-reader. If that fails, use mailto:std-c++@ncar.ucar.edu ]
- [ FAQ: http://reality.sgi.com/employees/austern_mti/std-c++/faq.html ]
- [ Policy: http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
- [ Comments? mailto:std-c++-request@ncar.ucar.edu ]
-